using B.S.XZYData.Api.Wrter.Application.Command.AssemblyWorkOrder;
using B.S.XZYData.Domain.ZSHH;
using B.S.XZYData.ErrorCode;
using B.S.XZYData.Infrastructure.Interface;
using MediatR;
using Microsoft.Extensions.Logging;
using System.Linq;

namespace B.S.XZYData.Api.Wrter.Application.Handler.AssemblyWorkOrder
{
    /// <summary>
    /// 更新产品完成数处理器
    /// </summary>
    public class UpdateProductCompletedQuantityHandler : IRequestHandler<UpdateProductCompletedQuantityCommand, ApiResult<bool>>
    {
        private readonly IBaseRepository<AssemblyWorkOrderProductDetail> _productDetailRepo;
        private readonly IBaseRepository<Domain.ZSHH.AssemblyWorkOrder> _assemblyWorkOrderRepo;
        private readonly ILogger<UpdateProductCompletedQuantityHandler> _logger;

        public UpdateProductCompletedQuantityHandler(
            IBaseRepository<AssemblyWorkOrderProductDetail> productDetailRepo,
            IBaseRepository<Domain.ZSHH.AssemblyWorkOrder> assemblyWorkOrderRepo,
            ILogger<UpdateProductCompletedQuantityHandler> logger)
        {
            _productDetailRepo = productDetailRepo;
            _assemblyWorkOrderRepo = assemblyWorkOrderRepo;
            _logger = logger;
        }

        public async Task<ApiResult<bool>> Handle(UpdateProductCompletedQuantityCommand request, CancellationToken cancellationToken)
        {
            var res = new ApiResult<bool>();
            try
            {
                // 查询产品明细是否存在
                var productDetail = await _productDetailRepo.GetValue(request.ProductDetailId);
                if (productDetail == null)
                {
                    res.Msg = "产品明细不存在";
                    res.Code = ApiEnum.Fail;
                    return await System.Threading.Tasks.Task.FromResult(res);
                }

                // 验证完成数不能超过数量
                if (request.CompletedQuantity > productDetail.Quantity)
                {
                    res.Msg = "完成数不能超过数量";
                    res.Code = ApiEnum.Fail;
                    return await System.Threading.Tasks.Task.FromResult(res);
                }

                // 更新产品明细的完成数
                productDetail.CompletedQuantity = request.CompletedQuantity;
                productDetail.Updator = request.Updator;
                productDetail.UpdatorDate = DateTime.Now;

                var updateResult = await _productDetailRepo.UpdateAsync(productDetail);
                if (updateResult <= 0)
                {
                    res.Msg = "更新产品完成数失败";
                    res.Code = ApiEnum.Fail;
                    return await System.Threading.Tasks.Task.FromResult(res);
                }

                // 重新计算并更新工单统计信息
                await UpdateWorkOrderStatisticsAsync(productDetail.WorkOrderId);

                res.Data = true;
                res.Code = ApiEnum.Success;
                res.Msg = "更新产品完成数成功";

                return await System.Threading.Tasks.Task.FromResult(res);
            }
            catch (Exception ex)
            {
                _logger.LogError($"更新产品完成数异常：{ex.Message}");
                res.Msg = "更新产品完成数异常：" + ex.Message;
                res.Code = ApiEnum.Error;
                return await System.Threading.Tasks.Task.FromResult(res);
            }
        }

        /// <summary>
        /// 更新工单统计信息（工单数、已结束工单数、单据进度）
        /// </summary>
        /// <param name="workOrderId">装配工单ID</param>
        private async System.Threading.Tasks.Task UpdateWorkOrderStatisticsAsync(long workOrderId)
        {
            try
            {
                // 查询该工单下的所有产品明细
                var productDetails = _productDetailRepo.GetAll()
                    .Where(x => !x.IsDeleted && x.WorkOrderId == workOrderId)
                    .ToList();

                if (!productDetails.Any())
                    return;

                // 1. 计算工单数（产品明细数据条数）
                var workOrderCount = productDetails.Count;

                // 2. 计算已结束工单数量（完成数之和）
                var completedWorkOrderCount = productDetails.Sum(x => x.CompletedQuantity ?? 0);

                // 3. 计算单据进度（已结束工单/工单数*100%）
                decimal documentProgress = 0;
                if (workOrderCount > 0)
                {
                    documentProgress = Math.Round((decimal)completedWorkOrderCount / workOrderCount * 100, 2);
                }

                // 4. 更新装配工单的统计信息
                var workOrder = await _assemblyWorkOrderRepo.GetValue(workOrderId);
                if (workOrder != null)
                {
                    workOrder.WorkOrderCount = workOrderCount;
                    workOrder.CompletedWorkOrderCount = completedWorkOrderCount;
                    workOrder.DocumentProgress = documentProgress;
                    workOrder.UpdatorDate = DateTime.Now;

                    await _assemblyWorkOrderRepo.UpdateAsync(workOrder);
                }
            }
            catch (Exception ex)
            {
                _logger.LogError($"更新工单统计信息异常：{ex.Message}");
            }
        }
    }
} 